package se.webbzon.oschi01.json;

import java.io.IOException;
import java.io.PrintStream;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;
import java.util.List;
import java.util.ListIterator;

public class JsonArray implements JsonType, List<JsonType> {
	
	/**
	 * 
	 */
	private static final long serialVersionUID = 8999828341962352756L;
	
	protected final List<JsonType> list = new ArrayList<JsonType>(); 
	
	public JsonArray() {}
	
	public JsonArray(JsonArray other) {
		for (JsonType obj : other.list) {
			list.add(obj.clone());
		}
	}
	
	public JsonArray(Collection<JsonType> objects) {
		list.addAll(objects);
	}
	
	public JsonArray(JsonType ... objects) {
		for (JsonType obj : objects)
			list.add(obj);
	}

	@Override public Type getType() {
		return JsonType.Type.Array;
	}
	
	@Override public String toString() {
		StringBuilder builder = new StringBuilder("[");
		boolean first = true;
		for (JsonType obj : list) {
			if (first)
				first = false;
			else
				builder.append(",");
			builder.append(obj.toString());
		}
		builder.append("]");
		return builder.toString();
	}
	
	@Override public int hashCode() {
		int hashCode = 0;
		for (JsonType obj : list) {
			hashCode += obj.hashCode();
		}
		return hashCode;
	}
	
	@Override public JsonArray clone() {
		return new JsonArray(this);
	}
	
	@Override public boolean equals(Object obj) {
		if (obj instanceof JsonArray) {
			JsonArray array = (JsonArray) obj;
			if (array.list.size() == list.size()) {
				Iterator<JsonType> it1 = list.iterator();
				Iterator<JsonType> it2 = array.list.iterator();
				while (it1.hasNext()) {
					if (!it1.next().equals(it2.next()))
						return false;
				}
				return true;
			} else
				return false;
		} else
			return false;
	}

	@Override public boolean add(JsonType e) {
		return list.add(e);
	}

	@Override public void add(int index, JsonType element) {
		list.add(index, element);
	}

	@Override public boolean addAll(Collection<? extends JsonType> c) {
		return list.addAll(c);
	}

	@Override public boolean addAll(int index, Collection<? extends JsonType> c) {
		return list.addAll(index, c);
	}

	@Override public void clear() {
		list.clear();
	}

	@Override public boolean contains(Object o) {
		return list.contains(o);
	}

	@Override public boolean containsAll(Collection<?> c) {
		return list.containsAll(c);
	}

	@Override public JsonType get(int index) {
		return list.get(index);
	}

	@Override public int indexOf(Object o) {
		return list.indexOf(o);
	}

	@Override public boolean isEmpty() {
		return list.isEmpty();
	}

	@Override public Iterator<JsonType> iterator() {
		return list.iterator();
	}

	@Override public int lastIndexOf(Object o) {
		return list.lastIndexOf(o);
	}

	@Override public ListIterator<JsonType> listIterator() {
		return list.listIterator();
	}

	@Override public ListIterator<JsonType> listIterator(int index) {
		return list.listIterator(index);
	}

	@Override public boolean remove(Object o) {
		return list.remove(o);
	}

	@Override public JsonType remove(int index) {
		return list.remove(index);
	}

	@Override public boolean removeAll(Collection<?> c) {
		return list.removeAll(c);
	}

	@Override public boolean retainAll(Collection<?> c) {
		return list.retainAll(c);
	}

	@Override public JsonType set(int index, JsonType element) {
		return list.set(index, element);
	}

	@Override public int size() {
		return list.size();
	}

	@Override public List<JsonType> subList(int fromIndex, int toIndex) {
		return list.subList(fromIndex, toIndex);
	}

	@Override public Object[] toArray() {
		return list.toArray();
	}

	@Override public <T> T[] toArray(T[] a) {
		return list.toArray(a);
	}

	@Override public void printTo(PrintStream ps) throws IOException {
		ps.print("[");
		boolean first = true;
		for (JsonType obj : list) {
			if (first)
				first = false;
			else
				ps.print(",");
			obj.printTo(ps);
		}
		ps.print("]");
	}
	
}
